import { useAuthStore } from "@/store/auth";
import { ContentType } from "@/types/message";

export class WebSocketClient {
  private ws: WebSocket | null = null;
  private readonly url: string;
  private reconnectAttempts = 0;
  private readonly maxReconnectAttempts = 5;
  private messageHandlers: Map<number, ((msg: any) => void)[]> = new Map();

  constructor() {
    console.log("Initializing WebSocket client");
    this.url = `ws://${window.location.hostname}:8080/websocket`;
    console.log("WebSocket URL:", this.url);
  }

  connect() {
    const authStore = useAuthStore();
    if (!authStore.user?.id) {
      console.error("User not logged in");
      return;
    }

    const wsUrl = `${this.url}/${authStore.user.id}`;
    console.log("Connecting to WebSocket:", wsUrl);

    this.ws = new WebSocket(wsUrl);

    // 添加原始事件监听
    this.ws.addEventListener("message", (event) => {
      console.log("Raw WebSocket message:", event.data);
    });

    this.setupEventHandlers();
  }

  private setupEventHandlers() {
    if (!this.ws) return;

    this.ws.onopen = () => {
      console.log("WebSocket connected successfully");
      console.log("WebSocket readyState:", this.ws?.readyState);
      this.reconnectAttempts = 0;
    };

    this.ws.onmessage = (event) => {
      try {
        const message = JSON.parse(event.data);
        console.log("Received message:", message);
        this.handleMessage(message);
      } catch (error) {
        console.error(
          "Failed to parse message:",
          error,
          "Raw data:",
          event.data
        );
      }
    };

    this.ws.onclose = (event) => {
      console.log("WebSocket connection closed:", {
        code: event.code,
        reason: event.reason,
        wasClean: event.wasClean,
      });
      this.handleDisconnect();
    };

    this.ws.onerror = (error) => {
      console.error("WebSocket error occurred:", error);
    };
  }

  private handleDisconnect() {
    if (this.reconnectAttempts < this.maxReconnectAttempts) {
      setTimeout(() => {
        this.reconnectAttempts++;
        this.connect();
      }, 1000 * Math.pow(2, this.reconnectAttempts));
    }
  }

  sendMessage(message: any) {
    if (this.ws && this.ws.readyState === WebSocket.OPEN) {
      if (message.contentType === ContentType.FILE) {
        const fileMessage = {
          ...message,
          fileName: message.fileName,
          fileSize: message.fileSize,
        };
        this.ws.send(JSON.stringify(fileMessage));
      } else {
        console.log("发送文本消息", message);
        this.ws.send(JSON.stringify(message));
      }
    } else {
      console.error("WebSocket未连接");
    }
  }

  addMessageHandler(messageType: number, handler: (msg: any) => void) {
    console.log("Adding handler for type:", messageType);
    const handlers = this.messageHandlers.get(messageType) || [];
    handlers.push(handler);
    this.messageHandlers.set(messageType, handlers);
    console.log(
      `Added handler for message type ${messageType}, total handlers:`,
      handlers.length
    );
  }

  removeMessageHandler(messageType: number, handler: (msg: any) => void) {
    const handlers = this.messageHandlers.get(messageType) || [];
    const index = handlers.indexOf(handler);
    if (index > -1) {
      handlers.splice(index, 1);
    }
  }

  disconnect() {
    if (this.ws) {
      this.ws.close();
      this.ws = null;
    }
  }

  handleMessage(message: any) {
    try {
      if (message === "heartbeat") {
        console.log("Heartbeat received");
        return;
      }

      const messageType = message.messageType || message.type;
      const handlers = this.messageHandlers.get(messageType) || [];

      if (handlers.length === 0) {
        console.warn(`No handlers registered for message type: ${messageType}`);
        return;
      }

      handlers.forEach((handler) => {
        try {
          console.log("Executing handler for message type:", messageType);
          handler(message);
        } catch (error) {
          console.error("Handler execution failed:", error);
        }
      });
    } catch (error) {
      console.error("Message handling failed:", error);
    }
  }

  isConnected(): boolean {
    return this.ws?.readyState === WebSocket.OPEN;
  }
}

// 创建单例
export const wsClient = new WebSocketClient();
